package com.ttpai.boot.lbs.service.ok;

import com.ttpai.boot.lbs.dao.MetroPointTimeDAO;
import com.ttpai.boot.lbs.model.MetroPointTimeVO;
import com.ttpai.boot.lbs.model.MetroPointVO;
import com.ttpai.boot.lbs.util.LLUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * Created by kail on 2017/3/11.
 */
@Service
public class MetroPointTimeService {

    @Autowired
    private MetroPointTimeDAO metroPointTimeDAO;

    @Autowired
    private MetroPointService metroPointService;

    private static final Map<String, Map<MetroPointTimeVO, MetroPointTimeVO>> cache = new HashMap<>();

    /**
     * 查找一个点指定时间内能到的地铁站
     * 1. 查找一个点最近的地铁站
     * 2. 根据地铁站名称找到最近的地铁站名称
     * 3. 根据找到的地铁站名称找到名为度
     */
    public List<MetroPointVO> findNearMetro(String cityName, Double lng, Double lat, Long timeSec) {
        MetroPointVO nearMetro = metroPointService.selectNearMetro(cityName, lng, lat);
        // 到地铁站前的时间
        double toMetroTime = LLUtil.linearDistance2Sec(nearMetro.getLng(), nearMetro.getLat(), lng, lat);

        // 到最近的地铁站之后只剩下五分钟就不再推荐地铁路线，因为做不了一站
        if (timeSec - toMetroTime < 60 * 5) {
            return new ArrayList<>();
        }

        List<MetroPointTimeVO> timeToGoMetros = selectMetroNearToMetro(cityName, nearMetro.getName(), timeSec);
        List<String> metroNames = new ArrayList<>();
        for (MetroPointTimeVO timeToGoMetro : timeToGoMetros) {
            metroNames.add(timeToGoMetro.getDistination());
        }
        return metroPointService.selectNearMetro(cityName, metroNames);
    }

    /**
     * 查找一个城市所有的地铁路线耗时
     * // FIXME redis 缓存
     */
    public Map<MetroPointTimeVO, MetroPointTimeVO> selectAllMeroTime(String cityName) {
        Map<MetroPointTimeVO, MetroPointTimeVO> timeVOMap = cache.get(cityName);
        if (null == timeVOMap || timeVOMap.isEmpty()) {
            List<MetroPointTimeVO> metroPointTimeVOS = metroPointTimeDAO.selectAllMetroPoint(new MetroPointTimeVO(cityName, "", ""));
            timeVOMap = new HashMap<>();
            for (MetroPointTimeVO pointTimeVO : metroPointTimeVOS) {
                timeVOMap.put(pointTimeVO, pointTimeVO);
            }
            cache.put(cityName, timeVOMap);
        }
        return timeVOMap;
    }

    /**
     * 从一个地铁站 一定时间内可以到的地铁站
     * // FIXME 从 Redis 缓存获得
     */
    public List<MetroPointTimeVO> selectMetroNearToMetro(String cityName, String metroName, Long timeSec) {
        List<MetroPointTimeVO> returnMetro = new ArrayList<>();

        Map<MetroPointTimeVO, MetroPointTimeVO> timeVOMap = selectAllMeroTime(cityName);
        for (MetroPointTimeVO pointTimeVO : timeVOMap.keySet()) {
            // 出发点
            if (pointTimeVO.getOrigin().equals(metroName)) {
                // 时间在指定范围内
                if (pointTimeVO.getUseTime() < timeSec) {
                    returnMetro.add(pointTimeVO);
                }
            }
        }
        return returnMetro;
    }


}
